﻿using Microsoft.International.Converters.PinYinConverter;
using System;
using System.Text;
using System.Text.RegularExpressions;

namespace Common.Library
{
    /// <summary>
    /// 字符串帮助类
    /// </summary>
    public static class StringHelper
    {
        #region 指定的字符串列表CnStr中检索符合拼音索引字符串

        /// <summary> 
        /// 汉字转化为拼音首字母
        /// </summary> 
        /// <param name="str">汉字</param> 
        /// <returns>首字母</returns> 
        public static string GetFirstPinyin(string str)
        {
            string r = string.Empty;
            foreach (char obj in str)
            {
                try
                {
                    ChineseChar chineseChar = new ChineseChar(obj);
                    string t = chineseChar.Pinyins[0].ToString();
                    r += t.Substring(0, 1);
                }
                catch
                {
                    r += obj.ToString();
                }
            }
            return r;
        }

        /// <summary> 
        /// 汉字转化为拼音
        /// </summary> 
        /// <param name="str">汉字</param> 
        /// <returns>全拼</returns> 
        public static string GetPinyin(string str)
        {
            string r = string.Empty;
            foreach (char obj in str)
            {
                try
                {
                    ChineseChar chineseChar = new ChineseChar(obj);
                    string t = chineseChar.Pinyins[0].ToString();
                    r += t.Substring(0, t.Length - 1);
                }
                catch
                {
                    r += obj.ToString();
                }
            }
            return r;
        }


        #endregion

        #region 截取字符长度
        /// <summary>
        /// 截取字符长度
        /// </summary>
        /// <param name="str">被截取的字符串</param>
        /// <param name="len">所截取的长度</param>
        /// <returns>子字符串</returns>
        public static string CutString(string str, int len)
        {
            if (str == null || str.Length == 0 || len <= 0)
            {
                return string.Empty;
            }
            int l = str.Length;
            #region 计算长度
            int clen = 0;
            while (clen < len && clen < l)
            {
                //每遇到一个中文，则将目标长度减一。
                if ((int)str[clen] > 128) { len--; }
                clen++;
            }
            #endregion
            if (clen < l)
            {
                return str.Substring(0, clen) + "...";
            }
            else
            {
                return str;
            }
        }

        /// <summary>
        /// //截取字符串中文 字母
        /// </summary>
        /// <param name="content">源字符串</param>
        /// <param name="length">截取长度！</param>
        /// <returns></returns>
        public static string SubTrueString(object content, int length)
        {
            string strContent = content.ToString();
            bool isConvert = false;
            int splitLength = 0;
            int currLength = 0;
            int code = 0;
            int chfrom = Convert.ToInt32("4e00", 16);    //范围（0x4e00～0x9fff）转换成int（chfrom～chend）
            int chend = Convert.ToInt32("9fff", 16);
            for (int i = 0; i < strContent.Length; i++)
            {
                code = Char.ConvertToUtf32(strContent, i);
                if (code >= chfrom && code <= chend)
                {
                    currLength += 2; //中文
                }
                else
                {
                    currLength += 1;//非中文
                }
                splitLength = i + 1;
                if (currLength >= length)
                {
                    isConvert = true;
                    break;
                }
            }
            if (isConvert)
            {
                return strContent.Substring(0, splitLength);
            }
            else
            {
                return strContent;
            }
        }

        /// <summary>
        /// 获取object转字符串长度
        /// </summary>
        /// <param name="content"></param>
        /// <returns></returns>
        public static int GetStringLenth(object content)
        {
            string strContent = content.ToString();
            int currLength = 0;
            int code = 0;
            int chfrom = Convert.ToInt32("4e00", 16);//范围（0x4e00～0x9fff）转换成int（chfrom～chend）
            int chend = Convert.ToInt32("9fff", 16);
            for (int i = 0; i < strContent.Length; i++)
            {
                code = Char.ConvertToUtf32(strContent, i);
                if (code >= chfrom && code <= chend)
                {
                    currLength += 2; //中文
                }
                else
                {
                    currLength += 1;//非中文
                }

            }
            return currLength;
        }
        #endregion

        #region 特殊字符操作

        /// <summary>  
        /// 检测是否有Sql危险字符  
        /// </summary>  
        /// <param name="str">要判断字符串</param>  
        /// <returns>判断结果</returns>  
        public static bool IsSafeSqlString(string str)
        {
            //过滤 ' --  
            string pattern1 = @"(\%27)|(\')|(\-\-)";
            //防止执行 ' or  
            string pattern2 = @"((\%27)|(\'))\s*((\%6F)|o|(\%4F))((\%72)|r|(\%52))";
            //防止执行sql server 内部存储过程或扩展存储过程  
            string pattern3 = @"\s+exec(\s|\+)+(s|x)p\w+";
            //SQL注入关键字
            string pattern4 = @"cmd |xor |declare |db_name\(\)| and| or|truncate |drop |table |count\(|from |select |insert into |update |delete |union |load_file\(|outfile\(";
            var par1 = Regex.IsMatch(str, pattern1);
            var par2 = Regex.IsMatch(str, pattern2);
            var par3 = Regex.IsMatch(str, pattern3);
            var par4 = Regex.IsMatch(str, pattern4);

            return !Regex.IsMatch(str, pattern1) 
                && !Regex.IsMatch(str, pattern2)
                && !Regex.IsMatch(str, pattern3) 
                && !Regex.IsMatch(str, pattern4);
        }

       
        /// <summary>  
        /// 删除SQL注入特殊字符  
        /// 加入对输入参数sql为Null的判断  
        /// </summary>  
        public static string StripSQLInjection(string sql)
        {
            if (!string.IsNullOrEmpty(sql))
            {
                //过滤 ' --  
                string pattern1 = @"(\%27)|(\')|(\-\-)";

                //防止执行 ' or  
                string pattern2 = @"((\%27)|(\'))\s*((\%6F)|o|(\%4F))((\%72)|r|(\%52))";

                //防止执行sql server 内部存储过程或扩展存储过程  
                string pattern3 = @"\s+exec(\s|\+)+(s|x)p\w+";

                sql = Regex.Replace(sql, pattern1, string.Empty, RegexOptions.IgnoreCase);
                sql = Regex.Replace(sql, pattern2, string.Empty, RegexOptions.IgnoreCase);
                sql = Regex.Replace(sql, pattern3, string.Empty, RegexOptions.IgnoreCase);
            }
            return sql;
        }

        /// <summary>
        /// SQL替换成安全特殊字符
        /// </summary>
        /// <param name="Parameter"></param>
        /// <returns></returns>
        public static string SQLSafe(string Parameter)
        {
            Parameter = Parameter.ToLower();
            Parameter = Parameter.Replace("'", "");
            Parameter = Parameter.Replace(">", ">");
            Parameter = Parameter.Replace("<", "<");
            Parameter = Parameter.Replace("\n", "<br>");
            Parameter = Parameter.Replace("\0", "·");
            return Parameter;
        }

        /// <summary>  
        /// 清除xml中的不合法字符  
        /// </summary>  
        /// <remarks>  
        /// 无效字符：  
        /// 0x00 - 0x08  
        /// 0x0b - 0x0c  
        /// 0x0e - 0x1f  
        /// </remarks>  
        public static string CleanInvalidCharsForXML(string input)
        {
            if (string.IsNullOrEmpty(input))
            {
                return input;
            }
            else
            {
                StringBuilder checkedStringBuilder = new StringBuilder();
                Char[] chars = input.ToCharArray();
                for (int i = 0; i < chars.Length; i++)
                {
                    int charValue = Convert.ToInt32(chars[i]);
                    if ((charValue >= 0x00 && charValue <= 0x08) || (charValue >= 0x0b && charValue <= 0x0c) || (charValue >= 0x0e && charValue <= 0x1f))
                    {
                        continue;
                    }
                    else
                    {
                        checkedStringBuilder.Append(chars[i]);
                    }
                }
                return checkedStringBuilder.ToString();
            }
        }

        /// <summary>  
        /// 改正sql语句中的转义字符  
        /// </summary>  
        public static string MashSQL(string str)
        {
            return (str == null) ? "" : str.Replace("\'", "'");
        }

        /// <summary>  
        /// 替换sql语句中的有问题符号 
        /// </summary>  
        public static string ChkSQL(string str)
        {
            return (str == null) ? "" : str.Replace("'", "''");
        }

        /// <summary>  
        ///  判断是否有非法字符 
        /// </summary>  
        /// <param name="strString"></param>  
        /// <returns>返回TRUE表示有非法字符，返回FALSE表示没有非法字符。</returns>  
        public static bool CheckBadStr(string strString)
        {
            bool outValue = false;
            if (strString != null && strString.Length > 0)
            {
                string[] bidStrlist = new string[9];
                bidStrlist[0] = "'";
                bidStrlist[1] = ";";
                bidStrlist[2] = ":";
                bidStrlist[3] = "%";
                bidStrlist[4] = "@";
                bidStrlist[5] = "&";
                bidStrlist[6] = "#";
                bidStrlist[7] = "\"";
                bidStrlist[8] = "net user";
                bidStrlist[9] = "exec";
                bidStrlist[10] = "net localgroup";
                bidStrlist[11] = "select";
                bidStrlist[12] = "asc";
                bidStrlist[13] = "char";
                bidStrlist[14] = "mid";
                bidStrlist[15] = "insert";
                bidStrlist[19] = "order";
                bidStrlist[20] = "exec";
                bidStrlist[21] = "delete";
                bidStrlist[22] = "drop";
                bidStrlist[23] = "truncate";
                bidStrlist[24] = "xp_cmdshell";
                bidStrlist[25] = "<";
                bidStrlist[26] = ">";
                string tempStr = strString.ToLower();
                for (int i = 0; i < bidStrlist.Length; i++)
                {
                    if (tempStr.IndexOf(bidStrlist[i]) != -1)
                    {
                        outValue = true;
                        break;
                    }
                }
            }
            return outValue;
        }


        #endregion

        #region 公用操作
        /// <summary> 
        /// 数字和字母字符串全部转成字母字符串
        /// </summary> 
        /// <param name="str">数字和字母字符串</param> 
        /// <returns>首字母</returns> 
        public static string ConvertToLetter(string str)
        {
            string r = string.Empty;
            string[] letters = { "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z"};
            foreach (char obj in str)
            {
                try
                {
                    int i = -1;
                    bool b = int.TryParse(obj.ToString(), out i);
                    if (b)
                    {
                        r += letters[i].ToString();
                    }
                    else
                    {
                        r += obj.ToString();
                    }
                }
                catch
                {
                    r += obj.ToString();
                }
            }
            return r;
        }
        #endregion
    }
}
